#include <string.h>

int cs_singleton_generator(FILE *farchivo,char *name)
{
	fprintf(farchivo,"\tprivate static %s instance = new %s();\n",name,name);
	fprintf(farchivo,"\tpublic static %s Instance{\n",name);
	fprintf(farchivo,"\t\t get {return instance;}\n");
	fprintf(farchivo,"\t}\n");
	fprintf(farchivo,"\tprivate %s(){}\n",name);
}
int cs_get_generator(FILE *farchivo, struct st_model *model){
	struct st_property_ls *properties;
	char strpropiedad[100];
	
	//getSimple
	fprintf(farchivo,"\tpublic DataTable get%s(){\n",model->name);
	fprintf(farchivo,"\t\treturn get%s(",model->name);
	properties=model->properties;
	while(properties!=NULL && properties->next!=NULL)
	{
		if(is_numeric_type(properties->property))
			fprintf(farchivo,"-1,");
		else
			fprintf(farchivo,"null,");
		properties=properties->next;		
	}
	if(properties!=NULL)
	{
		if(is_numeric_type(properties->property))
			fprintf(farchivo,"-1");
		else
			fprintf(farchivo,"NULL");
	}
	fprintf(farchivo,");\n\t}\n\n");
	
	
	
	// getCompleto	
	fprintf(farchivo,"\tpublic DataTable get%s(",model->name);
	properties=model->properties;
	while(properties!=NULL && properties->next!=NULL){
			fprintf(farchivo,"%s %s,",properties->property->type,properties->property->name);
			
		properties=properties->next;
	}
	if(properties!=NULL){
			fprintf(farchivo,"%s %s",properties->property->type,properties->property->name);

	}
	fprintf(farchivo,"){\n");
	fprintf(farchivo,"\t\tSqlCommand comando = conn.getCommand();\n");
	fprintf(farchivo,"\t\tcomando.CommandType = CommandType.StoredProcedure;\n");
	fprintf(farchivo,"\t\tcomando.CommandText = \"sp_%s_consultar\";\n",model->name);
	fprintf(farchivo,"\t\tstring host = System.Net.Dns.GetHostName();\n");
	fprintf(farchivo,"\t\tstring ip = System.Net.Dns.GetHostAddresses(host)[0].ToString();\n");
	fprintf(farchivo,"\t\tint ret_error=0;\n\n");
	properties=model->properties;
	while(properties!=NULL ){
		if(!is_numeric_type(properties->property))
			fprintf(farchivo,"\t\tif (%s != null)\n\t",properties->property->name);
		fprintf(farchivo,"\t\tcomando.Parameters.AddWithValue(\"@%s\", %s);\n",properties->property->name,properties->property->name);
		
		properties=properties->next;
	}
	
	
	fprintf(farchivo,"\t\tif (Configuracion.Instance.Usuario != null)\n");
	fprintf(farchivo,"\t\t\tcomando.Parameters.AddWithValue(\"@usrAlta\", Configuracion.Instance.Usuario.Id);\n");
	fprintf(farchivo,"\t\tif (Configuracion.Instance.Sistema != null)\n");
	fprintf(farchivo,"\t\t\tcomando.Parameters.AddWithValue(\"@sistema\", Configuracion.Instance.Sistema.Id);\n");
	fprintf(farchivo,"\t\tcomando.Parameters.AddWithValue(\"@ip\", ip);\n");
	fprintf(farchivo,"\t\tcomando.Parameters.AddWithValue(\"@host\", host);\n");
	fprintf(farchivo,"\t\tcomando.Parameters.AddWithValue(\"@ret_error\", ret_error);\n");
	fprintf(farchivo,"\t\treturn conn.executeQuery(comando);\n");
	fprintf(farchivo,"\t}\n\n");
	
	
	


}
int cs_save_generator(FILE *farchivo, struct st_model *model)
{
	struct st_property_ls *properties;
	char singular[100];
	char strpropiedad[100];
	strcpy(singular,model->name);
	singular[0]+=('a'-'A');
	
	//full save
	fprintf(farchivo,"\tpublic int guardar(%s %s, TransaccionMSSQL tran,bool lazy=true){\n",model->name,singular);
//	fprintf(farchivo,"\t\tint id=%s.Id\n",singular);
	fprintf(farchivo,"\t\tSqlCommand comando = tran.getCommand();\n");
	fprintf(farchivo,"\t\tcomando.CommandType = CommandType.StoredProcedure;\n");
	fprintf(farchivo,"\t\tcomando.CommandText = \"sp_%s_guardar\";\n",singular);
	
	fprintf(farchivo,"\t\tstring host = System.Net.Dns.GetHostName();\n");
	fprintf(farchivo,"\t\tstring ip = System.Net.Dns.GetHostAddresses(host)[0].ToString();\n");
	fprintf(farchivo,"\t\tint ret_error = 0;\n");
	
	properties=model->properties;
	while(properties!=NULL)
	{
		if(is_primitive_type(properties->property))
		{
			strcpy(strpropiedad,properties->property->name);
			strpropiedad[0]+=('A'-'a');
			fprintf(farchivo,"\t\tcomando.Parameters.AddWithValue(\"@%s\", %s.%s);\n",
				properties->property->name ,singular,strpropiedad);
		}
		else
		{
			strcpy(strpropiedad,properties->property->name);
			strpropiedad[0]+=('A'-'a');
			fprintf(farchivo,"\t\tcomando.Parameters.AddWithValue(\"@%s\", %s.%s.Id);\n",
				properties->property->name ,singular,strpropiedad);
			fprintf(farchivo,"\t\tif(!lazy){\n");
			fprintf(farchivo,"\t\t\tret_error=P%s.Instance.guardar(%s.%s,tran,lazy);\n",
				strpropiedad,singular,strpropiedad);
			fprintf(farchivo,"\t\t\tif(ret_error!=0) return ret_error;\n");
			fprintf(farchivo,"\t\t}\n");
		}
		properties=properties->next;
	}
	
	fprintf(farchivo,"\t\tcomando.ExecuteNonQuery();\n");
	fprintf(farchivo,"\t\tif (ret_error != 0)\n");
	fprintf(farchivo,"\t\t\treturn ret_error;\n");
	
//	fprintf(farchivo,"\t\t%s.Id=id;\n",singular);
	fprintf(farchivo,"\t\treturn ret_error;\n");
	fprintf(farchivo,"\t}\n\n");


	
	//short save
	fprintf(farchivo,"\tpublic int guardar(%s %s,bool lazy=true){\n",model->name,singular);
	fprintf(farchivo,"\t\tTransaccionMSSQL tran = (TransaccionMSSQL)conn.transaccion();\n");
	fprintf(farchivo,"\t\tint ret_error=guardar(%s, tran, lazy);\n",singular);
	fprintf(farchivo,"\t\tif (ret_error == 0) tran.commit();\n");
	fprintf(farchivo,"\t\telse tran.rollBack();\n");
	fprintf(farchivo,"\t\treturn ret_error;\n");
	fprintf(farchivo,"\t}\n\n");
}

int cs_pmodel_generator(struct st_model *model)
{
	char strmodel[100]="P";
	FILE *farchivo;
	char archivo[100];
	int error=OK;
	if(model==NULL)
		return INVALID_MODEL;
	else{
		sprintf(archivo,"%s.P%s.cs",NAMESPACE,model->name);
		farchivo=fopen(archivo, "w");
		printf("Inicia codificacion de %s\n",archivo);
		fprintf(farchivo,"public class P%s{\n",model->name);
		fprintf(farchivo,"\tprivate ConexionMSSQL conn = Persistencia.Instance.getConexion();\n");
		strcat(strmodel,model->name);
		cs_singleton_generator(farchivo,strmodel);
		cs_get_generator(farchivo,model);
		cs_save_generator(farchivo,model);
		fprintf(farchivo,"}\n\n");
		fflush(farchivo);
		fclose(farchivo);
		printf("Finaliza codificacion de %s\n\n",archivo);
	}
}

int cs_pmodels_generator( struct st_model_ls *models){
	while(models!=NULL)
	{
	 	cs_pmodel_generator(models->model);
	 	models=models->next;
	 }
	 return OK;	
}
